package org.port.weather;

import java.io.IOException;
import java.io.StringReader;
import java.sql.Date;
import java.util.ArrayList;

import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;
import javax.xml.xpath.XPath;
import javax.xml.xpath.XPathConstants;
import javax.xml.xpath.XPathExpressionException;
import javax.xml.xpath.XPathFactory;

import org.apache.http.NameValuePair;
import org.port.util.Log;
import org.port.util.Util;
import org.port.weather.WeatherActivity.Weather;
import org.port.weather.WeatherActivity.WeatherAction;
import org.port.weather.data.WeatherCP;
import org.port.weather.data.WeatherData;
import org.w3c.dom.Document;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import org.xml.sax.InputSource;
import org.xml.sax.SAXException;

import android.content.BroadcastReceiver;
import android.content.ContentValues;
import android.content.Context;
import android.content.Intent;

public class WeatherReceiver extends BroadcastReceiver {
	public static final String TAG = "WeatherRecevier";

	@Override
	public void onReceive(Context context, Intent intent) {
		// TODO Auto-generated method stub
		Log.i(TAG, "onReceive: " + intent.getAction());
		switch (WeatherAction.toAction(intent.getAction())) {
		case REQUEST_WEATHER_DATA:
			parseWeatherList(
					Util.getPrefer(context).getString(Util.LAST_GRID,
							"/wid/queryDFS.jsp?gridx=61&gridy=125"), null,
					context);
			break;

		default:
			break;
		}
	}

	/**
	 * @param grid
	 *            -> Address(Default:"/wid/queryDFS.jsp?gridx=61&gridy=125")
	 *            Request KMA Weather Data return Xml and Xml Parsing
	 *            InsertDataBase
	 * 
	 */
	public void parseWeatherList(String grid, ArrayList<WeatherData> wList,
			Context context) {
		Util.fileWrite(
				context,
				TAG + "-> "
						+ new Date(System.currentTimeMillis()).toLocaleString()
						+ ": parseWeatherList(grid= " + grid + ") ");
		ArrayList<NameValuePair> list = new ArrayList<NameValuePair>();
		String weatherData = Util.httpGetTypeReturn(
				WeatherActivity.KMA_DEFAULT_ADDRESS + grid, list);
		try {
			if (!"".equals(weatherData)) {
				StringReader sr = new StringReader(weatherData);
				Document doc = DocumentBuilderFactory.newInstance()
						.newDocumentBuilder().parse(new InputSource(sr));
				XPath path = XPathFactory.newInstance().newXPath();
				NodeList nList = (NodeList) path.evaluate("//data", doc,
						XPathConstants.NODESET);
				WeatherData item;
				for (int i = 0; i < nList.getLength(); i++) {
					item = parseWeatherItem(nList.item(i));
					// Database Update
					ContentValues cv = new ContentValues();
					cv.put(WeatherCP.DATE, item.getDay());
					cv.put(WeatherCP.STATE, item.getWfKor());
					cv.put(WeatherCP.TEMP, item.getTemp());
					cv.put(WeatherCP.RAIN, item.getR12());
					cv.put(WeatherCP.SNOW, item.getS12());
					cv.put(WeatherCP.WD, item.getWdKor());
					cv.put(WeatherCP.WS, item.getWs());
					cv.put(WeatherCP.WS, item.getWs());
					context.getContentResolver()
							.update(WeatherCP.WEATHER_URI,
									cv,
									WeatherCP.HOUR + " =? AND "
											+ WeatherCP.DATE + "=?",
									new String[] { item.getHour(),
											item.getDay() });
					Log.d(TAG, item.toString());
					if (wList != null) {
						wList.add(item);
					}
				}
				context.sendBroadcast(new Intent(
						WeatherAction.UPDATE_WEATHER_TABLE.toString()));
			} else {
				return;
			}
		} catch (ParserConfigurationException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (SAXException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (XPathExpressionException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}

	/**
	 * @param n
	 *            -> Weather Info Node this method is Weather Node Parsing and
	 *            Update DB data
	 */
	private WeatherData parseWeatherItem(Node n) {
		WeatherData item = new WeatherData();
		NodeList childList = n.getChildNodes();
		for (int i = 0; i < childList.getLength(); i++) {
			Node childNode = childList.item(i);
			if (childNode.getNodeType() == Node.ELEMENT_NODE) {
				switch (Weather.toString(childNode.getNodeName())) {
				case HOUR:
					item.setHour(childNode.getTextContent());
					break;
				case DAY:
					item.setDay(childNode.getTextContent());
					break;
				case TEMP:
					item.setTemp(childNode.getTextContent());
					break;
				case TMX:
					item.setTmx(childNode.getTextContent());
					break;
				case TMN:
					item.setTmn(childNode.getTextContent());
					break;
				case SKY:
					item.setSky(childNode.getTextContent());
					break;
				case PTY:
					item.setPty(childNode.getTextContent());
					break;
				case WFKOR:
					item.setWfKor(childNode.getTextContent());
					break;
				case WFEN:
					item.setWfEn(childNode.getTextContent());
					break;
				case POP:
					item.setPop(childNode.getTextContent());
					break;
				case R12:
					item.setR12(childNode.getTextContent());
					break;
				case S12:
					item.setS12(childNode.getTextContent());
					break;
				case WS:
					item.setWs(childNode.getTextContent());
					break;
				case WD:
					item.setWd(childNode.getTextContent());
					break;
				case WDKOR:
					item.setWdKor(childNode.getTextContent());
					break;
				case WDEN:
					item.setWdEn(childNode.getTextContent());
					break;
				case REH:
					item.setReh(childNode.getTextContent());
					break;
				default:
					Log.e(TAG, "parseWeatherItem not found case");
					break;
				}
			}
		}
		return item;
	}
}
